﻿namespace Core.Infra.Factories {
    using System;
    using FluentNHibernate.Cfg.Db;
    using FluentNHibernate.Cfg;
    using NHibernate;
    using System.Reflection;
    using FluentNHibernate.Conventions;
    using FluentNHibernate.Conventions.AcceptanceCriteria;
    using FluentNHibernate.Conventions.Instances;
    using FluentNHibernate.Conventions.Inspections;
    using NHibernate.Cfg;
    using NHibernate.Tool.hbm2ddl;

    public class SessionFactory {

        private static ISessionFactory _sessionFactory;

        public static ISessionFactory Create() {

            if (_sessionFactory == null) {
                _sessionFactory = Fluently.Configure()
                        .Database(MsSqlConfiguration.MsSql2005.ConnectionString(c => c.FromConnectionStringWithKey("MySqlFinanca")).ShowSql())
                        .Mappings(m => m.FluentMappings
                                        .AddFromAssembly(Assembly.GetExecutingAssembly()).Conventions.AddFromAssemblyOf<EnumConvention>())
                    //.ExposeConfiguration(BuildSchema)
                    .ExposeConfiguration(c => c.SetProperty("current_session_context_class", "web"))
                    .BuildSessionFactory();

                //_sessionFactory =  Fluently.Configure()
                //        .Database(MySQLConfiguration.Standard.ConnectionString(c => c.FromConnectionStringWithKey("MySqlFinanca")).ShowSql())
                //        .Mappings(m => m.FluentMappings
                //                        .AddFromAssembly(Assembly.GetExecutingAssembly()).Conventions.AddFromAssemblyOf<EnumConvention>())
                    //.ExposeConfiguration(BuildSchema)
                //    .ExposeConfiguration(c => c.SetProperty("current_session_context_class", "web"))
                //    .BuildSessionFactory();
            }

            return _sessionFactory;
        }

        private static void BuildSchema(Configuration config)
	    {
	        SchemaExport schema = new SchemaExport(config);
	        schema.Drop(false, true);
	        schema.Create(false, true);
	    }
    }

    public class EnumConvention : IPropertyConvention, IPropertyConventionAcceptance {
        #region IPropertyConvention Members

        public void Apply(IPropertyInstance instance) {
            instance.CustomType(instance.Property.PropertyType);
        }

        #endregion

        #region IPropertyConventionAcceptance Members

        public void Accept(IAcceptanceCriteria<IPropertyInspector> criteria) {
            criteria.Expect(x => x.Property.PropertyType.IsEnum);
        }

        #endregion
    }
}
